package com.wan37.client.message.received;

import com.google.protobuf.Message;
import com.googlecode.protobuf.format.JsonFormat;
import com.wan37.client.handler.ClientHandler;
import com.wan37.client.service.DelayThreadPool;
import com.wan37.client.service.PVEFightingService;
import com.wan37.client.service.PVPFightingService;
import com.wan37.client.service.SkillService;
import com.wan37.client.service.cache.RoleServiceCache;
import com.wan37.client.service.cache.UserServiceCache;
import com.wan37.protobuf.constant.*;
import com.wan37.protobuf.message.client2server.game.GameEntity;
import com.wan37.protobuf.message.client2server.game.GameFighting;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

/**
 * @author : luoyong
 * @date : 2020-07-10 12:27
 **/
@Component(PtoNum.ATTACKBROADCASTRESPONSE + "")
public class AttackBroadcastResponse implements ReceiveMsg {

    private final static Logger logger = LoggerFactory.getLogger(AttackBroadcastResponse.class);
    @Autowired
    private UserServiceCache userServiceCache;
    private ClientHandler clientHandler = ClientHandler.getInstance();
    @Autowired
    private RoleServiceCache roleServiceCache;
    @Autowired
    private PVEFightingService pveFightingService;
    @Autowired
    private PVPFightingService pvpFightingService;

    @Override
    public void execute(Message msg) {
        GameFighting.AttackBroadcastResponse attackBroadcastResponse = (GameFighting.AttackBroadcastResponse) msg;
        int code = attackBroadcastResponse.getCode();
        GameFighting.AttackResponse attackResponse = attackBroadcastResponse.getAttackResponse();
        String id = attackResponse.getAllRoleId();
        String skillId = attackResponse.getSkillId();
        switch (code) {
            case CommonFighting.ATTACK_SUCCESS:
                /**
                 * 判断返回的是角色还是boss，存在不同地方了
                 */
                if (roleServiceCache.getRoleInMap().containsKey(id)) {
                    GameEntity.Skill skill =  roleServiceCache.getRoleInMap().get(id).getSkillMap().get(attackResponse.getSkillId());
                    DelayThreadPool.add(id, skill);
                    GameEntity.Role role = roleServiceCache.getRoleInMap().get(id).getRole();
                    for (GameFighting.AttackResponse.AttackResult result : attackResponse.getResultList()) {
                        String resultId = result.getAllRoleId();
                        if (roleServiceCache.getRoleInMap().containsKey(resultId)) {
                            GameEntity.Role role1 = roleServiceCache.getRoleInMap().get(resultId).getRole();
                            playerAttackPlayer(id, resultId, role, result, skillId, role1);
                        } else if (SkillService.allRoleIdToSkillMap.containsKey(resultId)) {
                            GameEntity.AllRole monster = ClientHandler.allRoleMap.get(resultId);
                            playerAttackMonster(id, resultId, role, result, skillId, monster);
                        }
                    }
                    if (clientHandler.fightType == CommonFighting.PVP){
                        DelayThreadPool.schedule(()->pvpFightingService.playerSelectAttackObject(role), skill.getReading());
                    }else if (clientHandler.fightType == CommonFighting.PVE){
                        if (role.getAllRole().getStatus() == AllRoleLabel.STATUS_DIE) {
                            logger.info("{} 被砍死了！", role.getAllRole().getNickname());
                        } else {
                            boolean flag = false;
                            for (GameEntity.AllRole allRole1 : ClientHandler.allRoleMap.values()) {
                                if (allRole1.getLabel() == AllRoleLabel.MONSTER && allRole1.getStatus() != AllRoleLabel.STATUS_DIE) {
                                    DelayThreadPool.schedule(()->pveFightingService.playerAttackMonster(role, allRole1), skill.getReading());
                                    flag = true;
                                    break;
                                }
                            }
                            if (flag){
                                for (GameEntity.AllRole allRole1 : ClientHandler.allRoleMap.values()) {
                                    if (allRole1.getMP() > 0) {
                                        DelayThreadPool.schedule(()->pveFightingService.playerAttackMonster(role, allRole1), skill.getReading());
                                        break;
                                    }
                                }
                            }
                        }
                    }
                } else if (SkillService.allRoleIdToSkillMap.containsKey(id)) {
                    GameEntity.Skill skill = SkillService.allRoleIdToSkillMap.get(id).get(attackResponse.getSkillId());
                    DelayThreadPool.add(id, skill);
                    GameEntity.AllRole monster = ClientHandler.allRoleMap.get(id);
                    for (GameFighting.AttackResponse.AttackResult result : attackResponse.getResultList()) {
                        String resultId = result.getAllRoleId();
                        if (roleServiceCache.getRoleInMap().containsKey(resultId)) {
                            GameEntity.Role role1 = roleServiceCache.getRoleInMap().get(resultId).getRole();
                            monsterAttackPlayer(id, resultId, role1, result, skillId, monster);
                        }
                    }
                    if (clientHandler.fightType == CommonFighting.PVE){
                        if (monster.getStatus() == AllRoleLabel.STATUS_DIE) {
                            logger.info("{} 被砍死了！", monster.getNickname());
                        } else {
                            DelayThreadPool.schedule(()->pveFightingService.monsterSelectAttackObject(monster), skill.getReading());
                        }
                    }
                }
                break;
            case CommonFighting.ATTACK_ERROR_BOSS_DIE:
                logger.info("boss已被击杀！");
                pveFightingService.shutDownExecutor();
                break;
            case CommonFighting.ATTACK_ALL_ROLE_DIE:
                logger.info("战斗失败，请加大充钱力度！");
                pveFightingService.shutDownExecutor();
                break;
            case CommonFighting.ATTACK_ERROR:
                logger.info("发生错误！！");
                break;
            case CommonFighting.ATTACK_SUCCESS_DELAY_RESULT:
                /**
                 * 判断返回的是角色还是boss，存在不同地方了
                 */
                if (roleServiceCache.getRoleInMap().containsKey(id)) {
                    GameEntity.Role role = roleServiceCache.getRoleInMap().get(id).getRole();
                    for (GameFighting.AttackResponse.AttackResult result : attackResponse.getResultList()) {
                        String resultId = result.getAllRoleId();
                        if (roleServiceCache.getRoleInMap().containsKey(resultId)) {
                            GameEntity.Role role1 = roleServiceCache.getRoleInMap().get(resultId).getRole();
                            playerAttackPlayer(id, resultId, role, result, skillId, role1);
                        } else if (SkillService.allRoleIdToSkillMap.containsKey(resultId)) {
                            GameEntity.AllRole monster = ClientHandler.allRoleMap.get(resultId);
                            playerAttackMonster(id, resultId, role, result, skillId, monster);
                            if (role.getAllRole().getStatus() == AllRoleLabel.STATUS_DIE) {
                                logger.info("{} 被砍死了！", role.getAllRole().getNickname());
                            }
                        }
                    }
                } else if (SkillService.allRoleIdToSkillMap.containsKey(id)) {
                    GameEntity.AllRole monster = ClientHandler.allRoleMap.get(id);
                    for (GameFighting.AttackResponse.AttackResult result : attackResponse.getResultList()) {
                        String resultId = result.getAllRoleId();
                        if (roleServiceCache.getRoleInMap().containsKey(resultId)) {
                            GameEntity.Role role1 = roleServiceCache.getRoleInMap().get(resultId).getRole();
                            monsterAttackPlayer(id, resultId, role1, result, skillId, monster);
                            if (monster.getStatus() == AllRoleLabel.STATUS_DIE) {
                                logger.info("{} 被砍死了！", monster.getNickname());
                            }
                        }
                    }
                }
                break;
            case CommonFighting.ATTACK_ENEMY_ALL_ROLE_DIE:
                pveFightingService.shutDownExecutor();
                logger.info("成功击败对方！");
                break;
            case CommonFighting.GAME_FIGHTING_TIMEOUT:
                logger.info("战斗超时，战斗失败！！");
                pveFightingService.shutDownExecutor();
                clientHandler.sendMoveMessage(clientHandler.pre_scene);
                break;
            case CommonFighting.ATTACK_SELF_ALL_ROLE_DIE:
                logger.info("战斗失败！");
                pveFightingService.shutDownExecutor();
                break;
            case CommonFighting.ATTACK_ERROR_IS_DIE:
                logger.info("角色已经死亡，无法攻击!!!");
                break;
            case CommonFighting.ATTACK_ERROR_NOT_ENTITY:
                logger.info("目标不存在！！！");
                break;
            case CommonFighting.ATTACK_ERROR_ALL_ROLE_DIE:
                logger.info("敌方角色已被击杀！！！");
                break;
            case CommonFighting.ATTACK_ERROR_NOT_SKILL:
                logger.info("角色没有该技能！！");
                break;
            case CommonFighting.ATTACK_ERROR_NOT_ANY_SKILL:
                logger.info("角色没有任何技能，无法攻击!!!");
                break;
            case CommonFighting.ATTACK_ERROR_NOT_HP:
                logger.info("剩余蓝量不允许释放当前技能！！！");
                break;
            default:
                break;
        }
    }

    /**
     * 技能成功释放结算显示
     * @param id
     * @param resultId
     * @param role
     * @param result
     * @param skillId
     * @param monster
     */
    private void playerAttackMonster(String id, String resultId, GameEntity.Role role,
                                     GameFighting.AttackResponse.AttackResult result, String skillId, GameEntity.AllRole monster) {
        for (GameFighting.AttackResponse.AttackResult.NumberMap numberMap : result.getNumberMapList()) {
            if (numberMap.getCommonBase().equals(CommonBase.HP)) {
                GameEntity.Role role2 = role.toBuilder().setAllRole(role.getAllRole().toBuilder().setHP(numberMap.getResult()).build()).build();
                roleServiceCache.getRoleInMap().get(id).setRole(role2);
            }
            if (numberMap.getCommonBase().equals(CommonBase.MP)) {
                long oldMp = monster.getMP();
                GameEntity.AllRole monster2 = monster.toBuilder().setMP(numberMap.getResult()).build();
                ClientHandler.allRoleMap.put(resultId, monster2);
                logger.info("{} 使用 {} 技能，攻击了 {} ，造成了 {} 点伤害！",
                        role.getAllRole().getNickname(), roleServiceCache.getRoleInMap()
                                .get(id).getSkillMap().get(skillId).getName(),
                        ClientHandler.allRoleMap.get(resultId).getNickname(), oldMp - numberMap.getResult());
                logger.info("实体当前情况：{}", JsonFormat.printToString(ClientHandler.allRoleMap.get(resultId)));
            }
        }
    }

    /**
     * 技能成功释放结算显示
     * @param id
     * @param resultId
     * @param role1
     * @param result
     * @param skillId
     * @param monster
     */
    private void monsterAttackPlayer(String id, String resultId, GameEntity.Role role1,
                                     GameFighting.AttackResponse.AttackResult result, String skillId, GameEntity.AllRole monster) {
        for (GameFighting.AttackResponse.AttackResult.NumberMap numberMap : result.getNumberMapList()) {
            if (numberMap.getCommonBase().equals(CommonBase.HP)) {
                GameEntity.AllRole monster2 = monster.toBuilder().setHP(numberMap.getResult()).build();
                ClientHandler.allRoleMap.put(id, monster2);
            }
            if (numberMap.getCommonBase().equals(CommonBase.MP)) {
                long oldMp = role1.getAllRole().getMP();
                GameEntity.AllRole allRole = null;
                if (numberMap.getResult() <= 0) {
                    allRole = role1.getAllRole().toBuilder().setMP(numberMap.getResult()).setStatus(AllRoleLabel.STATUS_DIE).build();
                } else {
                    allRole = role1.getAllRole().toBuilder().setMP(numberMap.getResult()).build();
                }
                //更新对象插入
                GameEntity.Role role2 = role1.toBuilder().setAllRole(allRole).build();
                roleServiceCache.getRoleInMap().get(resultId).setRole(role2);
                logger.info("{} 使用 {} 技能，攻击了 {} ，造成了 {} 点伤害！",
                        monster.getNickname(), SkillService.allRoleIdToSkillMap
                                .get(id).get(skillId).getName(),
                        roleServiceCache.getRoleInMap().get(resultId).getRole().getAllRole().getNickname(),
                        oldMp - numberMap.getResult());
                logger.info("实体当前情况：{}", JsonFormat
                        .printToString(roleServiceCache.getRoleInMap().get(resultId).getRole()));
            }
        }
    }

    /**
     * 技能成功释放结算显示
     * @param id
     * @param resultId
     * @param role
     * @param result
     * @param skillId
     * @param role1
     */
    private void playerAttackPlayer(String id, String resultId, GameEntity.Role role,
                                    GameFighting.AttackResponse.AttackResult result, String skillId, GameEntity.Role role1) {
        long oldMp = role1.getAllRole().getMP();
        for (GameFighting.AttackResponse.AttackResult.NumberMap numberMap : result.getNumberMapList()) {
            if (numberMap.getCommonBase().equals(CommonBase.HP)) {
                GameEntity.Role role2 = role.toBuilder().setAllRole(role.getAllRole().toBuilder().setHP(numberMap.getResult()).build()).build();
                roleServiceCache.getRoleInMap().get(id).setRole(role2);
            }
            if (numberMap.getCommonBase().equals(CommonBase.MP)) {
                GameEntity.AllRole allRole = null;
                if (numberMap.getResult() <= 0) {
                    allRole = role1.getAllRole().toBuilder().setMP(numberMap.getResult()).setStatus(AllRoleLabel.STATUS_DIE).build();
                } else {
                    allRole = role1.getAllRole().toBuilder().setMP(numberMap.getResult()).build();
                }
                GameEntity.Role role2 = role1.toBuilder().setAllRole(allRole).build();
                roleServiceCache.getRoleInMap().get(resultId).setRole(role2);
                if (roleServiceCache.getRoleInMap().get(role.getAllRole().getAllRoleId()).getSkillMap().get(skillId).getLabel().startsWith(SkillLabel.FRIEND, 1)) {
                    logger.info("{} 使用 {} 技能，增幅 {} ，增加了 {} 点MP！",
                            role.getAllRole().getNickname(), roleServiceCache.getRoleInMap()
                                    .get(id).getSkillMap().get(skillId).getName(),
                            roleServiceCache.getRoleInMap().get(resultId).getRole().getAllRole().getNickname(),
                            numberMap.getResult() - oldMp);
                } else {
                    logger.info("{} 使用 {} 技能，攻击了 {} ，造成了 {} 点伤害！",
                            role.getAllRole().getNickname(), roleServiceCache.getRoleInMap()
                                    .get(id).getSkillMap().get(skillId).getName(),
                            roleServiceCache.getRoleInMap().get(resultId).getRole().getAllRole().getNickname(),
                            oldMp - numberMap.getResult());
                }
                logger.info("实体当前情况：{}", JsonFormat
                        .printToString(roleServiceCache.getRoleInMap().get(resultId).getRole()));
            }
        }
    }
}
